package graph.shapes;

import graph.parts.Shape;
import graph.parts.Shape.FaceForm;

import javax.vecmath.Vector2d;

import ogl.vecmath.Color;
import ogl.vecmath.Vector;
import ogl.vecmathimp.MatrixImp;
import additional.Vertex;

public class Tetrahedron extends Shape {
	private float el;
	private Vector middle = vec(0f,0f,0f);

	public Tetrahedron() {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		el = 0.5f;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}
	
	/**
	 * Konstruktor mit selbst definierter Kantenlänge
	 * @param el
	 */
	public Tetrahedron(float el) {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		this.el = el;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}

	/**
	 * Konstruktor mit selbst definierter Kantenlänge und selbst definietem Mittelpunkt
	 * @param el
	 * @param vector
	 */
	public Tetrahedron(float el, Vector middle) {
		super.setMatrix((MatrixImp) MatrixImp.identity);
		this.el = el;
		this.middle = middle;
		
		initPoints();
		initColors();
		initNormals();
		initTextureCoord();
		initVertices();
	}

	private void initPoints() {
		ff = FaceForm.TRIANGLES;
		
		Float xVer = middle.x();
		Float yVer = middle.y();
		Float zVer = middle.z();
		
		p = new Vector[]{ 
				vec(el*2.2f/3+ xVer, yVer, el/3 + zVer), 
				vec(-el*2.2f/3 + xVer, yVer, el/3 + zVer),
				vec(xVer, yVer, -el*2/3 + zVer), 
				vec(xVer, el + yVer, zVer), 
		};
	}

	private void initColors() {
		c = new Color[]{ 
			      col(1, 0, 0), 
			      col(1, 0, 0), 
			      col(1, 0, 0), 
			      col(1, 0, 0)
		};
	}

	private void initNormals() {
		Vector u;
		Vector v;
		
		// front
		u = p[1].sub(p[0]);
		v = p[3].sub(p[0]);
		Vector nf = v.cross(u);
		
		// left
		u = p[2].sub(p[1]);
		v = p[3].sub(p[1]);
		Vector nl = v.cross(u);
		
		// right
		u = p[2].sub(p[0]);
		v = p[3].sub(p[0]);
		Vector nr = u.cross(v);
		
		n = new Vector[] {
				vec(0, -1, 0),
		        nl,
		        nr,
		        nf,
			};
	}

	private void initTextureCoord() {
		t = new Vector2d[4];
		    t[0] = new Vector2d (0f, 0f);
		    t[1] = new Vector2d (0f, 1f);
		    t[3] = new Vector2d (1f, 1f);
		    t[2] = new Vector2d (1f, 0f);
	}

	private void initVertices() {
		vertices = new Vertex[] {
			    // bottom 
			    v(p[0], c[0], n[0], t[0]), 
			    v(p[1], c[1], n[0], t[1]), 
			    v(p[2], c[2], n[0], t[2]),
			    // left side
			    v(p[1], c[1], n[1], t[0]), 
			    v(p[2], c[2], n[1], t[1]), 
			    v(p[3], c[3], n[1], t[2]), 
			    // right  side
			    v(p[0], c[1], n[2], t[0]), 
			    v(p[2], c[2], n[2], t[1]), 
			    v(p[3], c[3], n[2], t[2]),
			    // front side
			    v(p[0], c[1], n[3], t[0]), 
			    v(p[1], c[1], n[3], t[1]), 
			    v(p[3], c[3], n[3], t[2])
		};
		
		initVertexData();
	}

}
